package com.night.icm.service.base.service;

import com.github.wenhao.jpa.PredicateBuilder;
import com.github.wenhao.jpa.Specifications;
import com.night.icm.common.exception.NoSuchDataException;
import com.night.icm.common.jpa.PageHelper;
import com.night.icm.common.night_enum.CourseBaseType;
import com.night.icm.common.service.PageDataUtil;
import com.night.icm.common.utils.PageDataDTO;
import com.night.icm.common.utils.SimpleDataDTO;
import com.night.icm.model.base.CourseTypeDTO;
import com.night.icm.persistence.base.entity.CourseType;
import com.night.icm.persistence.base.repository.CourseTypeRepository;
import com.night.icm.service.base.mapper.CourseTypeMapper;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.Optional;

/**
 * CourseTypeServiceImpl
 *
 * @author Liao ZhiYong
 * @date 2020/2/6
 */
@Service
@Transactional(readOnly = true, rollbackFor = Exception.class)
public class CourseTypeServiceImpl implements CourseTypeService {

    private final CourseTypeMapper courseTypeMapper;
    private final CourseTypeRepository courseTypeRepository;

    @Autowired
    public CourseTypeServiceImpl(CourseTypeMapper courseTypeMapper, CourseTypeRepository courseTypeRepository) {
        this.courseTypeMapper = courseTypeMapper;
        this.courseTypeRepository = courseTypeRepository;
    }

    /**
     * 分页查询课程类型
     *
     * @param page           页号，从0开始
     * @param size           每页记录条数
     * @param sort           排序字段，例如：字段1,asc,字段2,desc
     * @param code           课程详细类型编号
     * @param name           课程详细类型名称
     * @param courseBaseType 课程基础类型
     * @return 课程类型
     */
    @Override
    public PageDataDTO<CourseTypeDTO> findOnePage(int page, int size, String sort, String code, String name, CourseBaseType courseBaseType) {
        PredicateBuilder<CourseType> pb = Specifications.<CourseType>and()
                .like(StringUtils.isNotBlank(code), "code", "%" + code + "%")
                .like(StringUtils.isNotBlank(name), "name", "%" + name + "%")
                .eq(courseBaseType != null, "courseBaseType", courseBaseType);
        Page<CourseType> page1 = this.courseTypeRepository.findAll(pb.build(), PageHelper.generatePageRequest(page, size, sort));
        List<CourseTypeDTO> courseTypes = this.courseTypeMapper.toList(page1.getContent());
        return PageDataUtil.toPageData(page1, courseTypes);
    }

    /**
     * 新增课程类型
     *
     * @param courseTypeDTO 课程类型信息
     * @return 课程类型信息
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public CourseTypeDTO create(CourseTypeDTO courseTypeDTO) {
        CourseType courseType = this.courseTypeMapper.toEntity(courseTypeDTO);
        CourseType save = this.courseTypeRepository.save(courseType);
        return this.courseTypeMapper.toDTO(save);
    }

    /**
     * 删除课程类型
     *
     * @param id 课程类型id
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void delete(String id) {
        this.courseTypeRepository.deleteById(Long.valueOf(id));
    }

    /**
     * 更新课程类型信息
     *
     * @param id            课程类型id
     * @param courseTypeDTO 课程类型信息
     * @return 课程类型信息
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public CourseTypeDTO update(String id, CourseTypeDTO courseTypeDTO) {
        Optional<CourseType> courseTypeOptional = this.courseTypeRepository.findById(Long.valueOf(id));
        if (!courseTypeOptional.isPresent()) {
            throw new NoSuchDataException(id);
        }
        CourseType courseType = courseTypeOptional.get();
        this.courseTypeMapper.updateEntity(courseTypeDTO, courseType);
        this.courseTypeRepository.save(courseType);
        return this.courseTypeMapper.toDTO(courseType);
    }

    /**
     * 根据id查找课程类型信息
     *
     * @param id 课程类型id
     * @return 课程类型信息
     */
    @Override
    public CourseTypeDTO findById(String id) {
        Optional<CourseType> courseTypeOptional = this.courseTypeRepository.findById(Long.valueOf(id));
        if (!courseTypeOptional.isPresent()) {
            throw new NoSuchDataException(id);
        }
        CourseType courseType = courseTypeOptional.get();
        return this.courseTypeMapper.toDTO(courseType);
    }

    /**
     * 查找所有课程类型信息，可选择排序
     *
     * @param param   排序参数
     * @param pattern 排序模式: asc/desc
     * @return 课程类型信息
     */
    @Override
    public List<CourseTypeDTO> findAll(String param, String pattern) {
        String keyType = "asc";
        Sort sort;
        if (keyType.equals(pattern)) {
            sort = new Sort(Sort.Direction.ASC, param);
        } else {
            sort = new Sort(Sort.Direction.DESC, param);
        }
        List<CourseType> all = this.courseTypeRepository.findAll(sort);
        return this.courseTypeMapper.toList(all);
    }

    /**
     * 检查课程详细类型编号是否已存在
     *
     * @param code 课程详细类型编号
     * @return 是否存在
     */
    @Override
    public SimpleDataDTO<Boolean> checkCodeExist(String code) {
        SimpleDataDTO<Boolean> simpleDataDTO = new SimpleDataDTO<>();
        CourseType courseType = this.courseTypeRepository.findByCode(code);
        simpleDataDTO.setData(courseType != null);
        return simpleDataDTO;
    }
}